package com.umfwechat.lightprogram.controller.my;

import java.io.File;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import net.sf.json.JSONObject;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;

import com.thoughtworks.xstream.XStream;
import com.thoughtworks.xstream.io.xml.DomDriver;
import com.umfwechat.common.code.RetCode;
import com.umfwechat.common.constant.CommonConsts;
import com.umfwechat.common.prop.UmfPropModel;
import com.umfwechat.util.AgentBillDirFilter;
import com.umfwechat.util.DateTimesUtil;
import com.umfwechat.util.EmailXmlUtil;
import com.umfwechat.util.PropertyUtil;
import com.umfwechat.util.ReqMessageUtil;
import com.umfwechat.util.ZipUtil;
import com.umfwechat.util.email.MailSenderInfo;
import com.umfwechat.util.email.SendMailUtil;
import com.umpay.sp.model.common.ResMessage;
import com.umpay.sp.model.saas.AgentPerm;
import com.umpay.sp.service.saas.remote.AgentPermServiceRemote;
/**
 * 代理商对账邮件
 * @author llb
 *
 */
@Controller
@RequestMapping("/agentBill")
public class SendBillEmailController {
	private static Logger logger = LoggerFactory.getLogger(SendBillEmailController.class);
	@Resource
	private AgentPermServiceRemote agentPermServiceRemote;
	/**
	 * 代理商对账邮件
	 * @param request
	 * @param response
	 * @return
	 * @throws Exception
	 */
	@RequestMapping("/sendAgentBillEmail")
	@ResponseBody
	public JSONObject sendAgentBillEmail (HttpServletRequest request, HttpServletResponse response) throws Exception{
		JSONObject resJson= new JSONObject();
		resJson.put(CommonConsts.RETCODE, RetCode.SUCCESS);
		resJson.put(CommonConsts.RETMSG, "对账邮件将在3-5分钟后送达，请注意查收！");
		//通过流的方式获取前端的参数
		String reqJSON=  (String) request.getAttribute(CommonConsts.REQUESTDATA);
		JSONObject json = null;
		try {
			json = JSONObject.fromObject(reqJSON);
		} catch (Exception e) {
			resJson.put(CommonConsts.RETCODE, "0001");
			resJson.put(CommonConsts.RETMSG, "获取请求参数失败");
			logger.info("【发送对账文件接口异常】----#---------#--获取请求参数失败异常--#---------#--" + e);
			return resJson;
		}
		final String agentId=json.optString(CommonConsts.LOGINAGENTID);//代理商编号
		String dateSrc=json.optString("billDate");//日期2017-07-11
		
//		String assistId =(String) json.get(CommonConsts.LOGINASSISTID);//登录账号
//		String userId = (String) json.get(CommonConsts.LOGINUSERID);//业务员编号
//		if(!"admin".equals(userId)){
//			boolean b = getPermission(userId,agentId,assistId,3);	//1:分润查询; 2:代理商商户查询; 3:对账文件获取
//			if(!b){
//				resJson.put(CommonConsts.RETCODE, "0001");
//				resJson.put(CommonConsts.RETMSG, "您没有操作权限");
//				return resJson;
//			}
//		}
		
		final String date=dateSrc.substring(0, 4)+dateSrc.substring(5, 7)+dateSrc.substring(8, 10);
		final String email=json.optString("email");//邮箱
		//查询多级代理商，获取所有下级代理商编号，包含自己代理商编号
		Map<String, Object> resQ = queryAgentRel(agentId, "2");//0或不传-查询完整级别关系,1-查询直接下级,2-查询所有下级,3-查询直接上级,4-查询所有上级
		String retCodeQ=(String)resQ.get("retCode");
		if(!"0000".equals(retCodeQ)){
			json.put(CommonConsts.RETCODE, "0001");
			json.put(CommonConsts.RETMSG, "服务器异常，请稍后再试");
			return json;
		}
		Map<String, Object> agentMetaMap =  (Map<String, Object>) resQ.get("agentMetaMap");
		Map<String, List<String>> supAgentLevelRelMap=(Map<String, List<String>>) resQ.get("supAgentLevelRelMap");
		Map<String, Map<String, String>> agentDataList = (Map<String, Map<String, String>>)resQ.get("agentMap");
		Map<String, String> currentAgentData = agentDataList.get(agentId);//当前代理商的基本信息
		final String agentShortName = currentAgentData.get("agentShortName");
		Integer min = Integer.valueOf( agentMetaMap.get("minLevel").toString()) ;
		Integer max =  Integer.valueOf( agentMetaMap.get("maxLevel").toString()) ; 
		final List<String> agentIds = new ArrayList<String>();//所有代理商编号
		for(int i = max;i<=min;i++){
			List<String> listA  = (List<String>) agentMetaMap.get("agent["+i+"]List");
			agentIds.addAll(listA);
		}
		logger.info("获取到的所有代理商编号："+agentIds);
		//*********************************查找结算文件开始***********************************************************
		// 新启动一个线程 发送邮件
		new Thread() {
			public void run(){
				logger.info("【查找结算文件开始】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
				//文件路径集合
				List<String> dayFilePathList = getBatchFilePath(agentIds, date);
				logger.info("【查找结算文件结束】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
				try {
					if(dayFilePathList == null || dayFilePathList.size() == 0){
						//不存在就发有附件的邮件
						String noAgentBillTemplateEmail=UmfPropModel.INSTANCE.getPropValue("noAgentBillTemplateEmail");
						logger.info("【对账模板路径】noAgentBillTemplateEmail="+noAgentBillTemplateEmail);
						sendMail(noAgentBillTemplateEmail, email, agentShortName, agentId, date, null);
						logger.info("【结算文件还未生成邮件已发送，请查收】");
						return ;
					}
					logger.info("【结算文件总个数：】"+dayFilePathList.size());
					//存在就发有附件的邮件
					logger.info("【结算文件打包开始】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
					//文件打包
					//文件打包路径
					String zipdownloadUrl =UmfPropModel.INSTANCE.getPropValue("saas.AgentSettleDetail.zipdownload");
					String zipdownload=zipdownloadUrl.replace("{yyyyMMdd}", date);
					logger.info("【文件打包路径】zipdownload="+zipdownload);
					File file = new File(zipdownload);//打包地址
					if (!file.exists()){
						file.mkdirs();
					}
					String zipFileName = date + "-" + agentId + ".zip";
					File zipFile = new File(zipdownload,File.separatorChar + zipFileName);
					//打包文件
					ZipUtil.zip(zipFile, dayFilePathList);
					logger.info("【结算文件打包结束】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
					zipFile = new File(zipdownload, File.separatorChar + zipFileName);
					if (zipFile.exists()) {
						List<File> fileList = new ArrayList<File>();
						fileList.add(zipFile);
						//发邮件
						String agentBillTemplateEmail=UmfPropModel.INSTANCE.getPropValue("agentBillTemplateEmail");
						logger.info("【对账模板路径】agentBillTemplateEmail="+agentBillTemplateEmail);
						sendMail(agentBillTemplateEmail, email, agentShortName, agentId, date, fileList);
						logger.info("【对账单邮件已发送，请查收】");
					}
				} catch (Exception e) {
					logger.error("【发送邮件失败】" + e);
					return;
				}
			}
		}.start();
		logger.info("【对账邮件将在3-5分钟后送达，请注意查收】");
		return resJson;
	}
	/**
	 * 发送邮件
	 * 
	 * @param templateUrl 邮件内容模板
	 * @param email 收件邮箱
	 * @param storeShortName 商户简称
	 * @param storeId 商户号
	 * @param billMonth 账单年月
	 * @param fileList 附件
	 * @throws ParseException 
	 */
	private void sendMail(String templateUrl, String email, String agentShortName, String agentId, String date, List<File> fileList) throws ParseException{
		logger.info("【发送邮件开始】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
		Calendar calendar = Calendar.getInstance();
		String currentDate = DateTimesUtil.date8(calendar.getTime());
		Date formatDate = new SimpleDateFormat("yyyyMMdd").parse(date);
		System.out.println(formatDate);
		String format = new SimpleDateFormat("yyyy年MM月dd").format(formatDate);
		//发邮件
		String mailto = email;
		String subject = format+"日享云业务对账文件";
		//邮件内容			
		Map<String, String> map = new HashMap<String, String>();
		map.put("agentShortName", agentShortName);
		map.put(CommonConsts.AGENTID, agentId);
		map.put(CommonConsts.DATE, format);
		map.put(CommonConsts.YYYY, currentDate.substring(0,4));
		map.put(CommonConsts.MM, currentDate.substring(4,6));
		map.put(CommonConsts.DD, currentDate.substring(6,8));
		MailSenderInfo mailSenderInfo = new MailSenderInfo();
		mailSenderInfo.setToAddress(email);
		EmailXmlUtil.emailXmlRead(templateUrl, mailSenderInfo, map);
		String mailContent = mailSenderInfo.getContent();
		for (String s : map.keySet()) {
			mailContent = mailContent.replaceAll(s, map.get(s));
		}
		//发邮件
		if(fileList == null){
			SendMailUtil.sendMail(mailto, subject, mailContent);
		}else{
			SendMailUtil.sendMail(mailto, subject, mailContent, fileList);
		}
		logger.info("【发送邮件结束】" + DateTimesUtil.date(DateTimesUtil.formatTime16Str));
	}
	
	/**
	 * 文件路径集合
	 */
	private List<String> getBatchFilePath(List<String> agentIds, String date){
		///usr/mpsp/AppData/saas/settle/agent/{yyyyMMdd}
		String dirUrl= PropertyUtil.getStrValue("umfWeChatPlat_appConf.properties", "saas.AgentSettleDetail.out.path");
		String excelPath = dirUrl.replace("{yyyyMMdd}", date);
		logger.info("【日结算文件路径】 excelPath = " + excelPath);
		List<String> fileNameList = new ArrayList<String>();
		//过滤同时含有代理商编号和日期的文件名
		for (String agentId : agentIds) {
			AgentBillDirFilter agentBillDirFilter = new AgentBillDirFilter(agentId, date);
			//获取文件列表
			File file = new File(excelPath);
			String[] names = file.list(agentBillDirFilter);//路径下所有文件
			if(names != null){
				for (String name : names) {//遍历文件名，拼接路径和文件名
					String pathName = excelPath + name;//拼接文件存储路径和文件名
					fileNameList.add(pathName);
				}
			}
		}
		logger.info("【日结算所有的文件集合】 ： " + fileNameList);
		return fileNameList;
	}

	private Map<String, Object> queryAgentRel(String agentId,String type) {
	    Map<String, Object> req = ReqMessageUtil.makeReqCrmMap();
	    req.put("agentId", agentId);
	    req.put("relType", type);
		Map<String, Object> res = null;
		try {
			XStream xstream = new XStream(new DomDriver());
			// URL配置文件取
			String url=UmfPropModel.INSTANCE.getPropValue("agent.crm.queryAgentRel");
			//调用受理注销用户标识接口
			logger.info("【查询代理商多级关系接口】入参：" + req.toString()+"请求路径url="+url);
			res =  (Map<String, Object>) com.umfwechat.util.HttpUtil.getResObjPost(url, xstream, req);	
		} catch (Exception e) {
			logger.info("【调用查询代理商多级关系接口失败!】",e);
			res.put(CommonConsts.RETCODE, "0001");
			res.put(CommonConsts.RETMSG,"服务器异常，请稍后再试");	
			return res;
		}
		if(res==null){
			res.put(CommonConsts.RETCODE, "0001");
			res.put(CommonConsts.RETMSG, "服务器异常，请稍后再试");
			return res;
		}
		logger.info("【查询代理商多级关系接口】出参：" + res.toString());				
		return res;
	}
	/**
	 * @param salesmanId业务员名称
	 * @param agentId代理商编号
	 * @param assistId登录账号
	 * @param type菜单类型(1:分润查询; 2:代理商商户查询; 3:对账文件获取)
	 * @return
	 */
	public boolean getPermission(String salesmanId, String agentId, String assistId, Integer type){
		com.umpay.sp.model.common.ReqMessage reqMess = ReqMessageUtil.makeSpReq();
		reqMess.put(CommonConsts.SALESMANID, salesmanId);
		reqMess.put(CommonConsts.AGENTID,agentId);
		reqMess.put(CommonConsts.ASSISTID,assistId);
		ResMessage res = null;
		try {
			logger.info("【获取代理商权限控制接口】输入参数：" + reqMess);
			res = agentPermServiceRemote.getAgentPermByPri(reqMess);
			logger.info("【获取代理商权限控制接口】输出参数：" + res);
		} catch (Exception e) {
			return false;
		}
		String retCode = res.getRetCode();
		if (!RetCode.SUCCESS.equals(retCode)) {
			return false;
		}
		AgentPerm agentPerm = (AgentPerm) res.getResMap().get("agentPerm");
		if (agentPerm == null) {
			return false;
		}
		if(type == 1){	//分润查询权限
			if("1".equals(agentPerm.getSearchProfitPerm())){
				return true;
			}
		}
		if(type == 2){	//代理商商户查询权限
			if("1".equals(agentPerm.getSearchStorePerm())){
				return true;
			}
		}
		if(type == 3){	//对账文件获取权限
			if("1".equals(agentPerm.getFetchBillDocPerm())){
				return true;
			}
		}
		return false;
	}
	public static void main(String[] args) throws Exception {
		SendBillEmailController controller= new SendBillEmailController();
		controller.sendAgentBillEmail(null, null);
	}
}
